/**
  ******************************************************************************
  * @author     Chris
  * @since      2024/6/18 22:21
  *
  * @file       pd_adc_reg.h
  * @brief      Header file of ADC Regular group peripheral driver.
  *
  * @note       This file contains the ADC Regular group object declaration.
  *
  * @warning    None.
  ******************************************************************************
  * Change Logs:
  *   Date          Author       Notes
  *   2024/6/18     Chris        the first version
  *
  ******************************************************************************
  */


#ifndef JLC_SKY_ADC_REG_H
#define JLC_SKY_ADC_REG_H

#include "pd_adc.h"

struct ADCRegularVtbl;

/** @defgroup Object properties
  * @{
  */
typedef struct {
    ADCBase *adcBase;


    uint32_t TriggerSource;    // ADC trigger source: TIM, EXT, Software
    uint32_t SequencerLength;  // Discontinuous Mode(ADC_SQR1_L, Bits 23:20 L[3:0])
    uint32_t SequencerDiscont; // Discontinuous Mode(ADC_CR1_DISCEN | ADC_CR1_DISCNUM)
    uint32_t ContinuousMode;   // ADC Mode: single or continuous
    uint32_t DMATransfer;      // ADC DMA transfer


    // ADCRegular virtual table
    struct ADCRegularVtbl *vptr;
} ADCRegular; /* extends from {@see ADCBase} */
/**
 * @}
 */

/** @defgroup Object virtual table definition
  * @{
  */
struct ADCRegularVtbl {
    void (*init)(const ADCRegular *this);

    void (*start)(const ADCRegular *this);

    uint16_t (*get_value)(const ADCRegular *this, uint32_t Rank, uint32_t Channel, uint32_t SamplingTime);
};
/**
 * @}
 */

/** @defgroup Object constructor and member function declaration
  * @{
  */
void ADCRegular_constructor(ADCRegular *this, ADCBase *adcBase, uint32_t TriggerSource, uint32_t SequencerLength,
                            uint32_t ContinuousMode, uint32_t DMATransfer);
/**
 * @}
 */

/** @defgroup Object virtual table function implementation
  * @{
  */
static inline void ADCRegular_init(const ADCRegular *this) {
    this->vptr->init(this);
}

static inline void ADCRegular_start(const ADCRegular *this) {
    this->vptr->start(this);
}

static inline uint16_t ADCRegular_getValue(const ADCRegular *this, const uint32_t Rank, const uint32_t Channel,
                                           const uint32_t SamplingTime) {
    return this->vptr->get_value(this, Rank, Channel, SamplingTime);
}
/**
 * @}
 */


#endif //JLC_SKY_ADC_REG_H
